package com.mico.micochange.trade;

import com.alibaba.fastjson.JSONObject;
import com.mico.micochange.common.ExchangeCacheUtils;
import com.mico.micochange.common.RedisUtils;
import com.mico.micochange.server.MicoThread;
import com.mico.xchange.Exchange;
import com.mico.xchange.ExchangeFactory;
import com.mico.xchange.binance.BinanceExchange;
import com.mico.xchange.binance.dto.meta.exchangeinfo.Filter;
import com.mico.xchange.binance.dto.meta.exchangeinfo.Symbol;
import com.mico.xchange.binance.service.BinanceAccountService;
import com.mico.xchange.binance.service.BinanceMarketDataService;
import com.mico.xchange.binance.service.BinanceTradeService;
import com.mico.xchange.bitstamp.BitstampAuthenticatedV2;
import com.mico.xchange.bitstamp.BitstampExchange;
import com.mico.xchange.bitstamp.dto.trade.BitstampOrder;
import com.mico.xchange.bitstamp.service.BitstampTradeServiceRaw;
import com.mico.xchange.currency.CurrencyPair;
import com.mico.xchange.dto.Order;
import com.mico.xchange.dto.marketdata.Ticker;
import com.mico.xchange.dto.trade.MarketOrder;
import com.mico.xchange.fcoin.FCoinExchange;
import com.mico.xchange.fcoin.dto.trade.FCoinSide;
import com.mico.xchange.fcoin.service.FCoinTradeServiceRaw;
import com.mico.xchange.huobi.HuobiExchange;
import com.mico.xchange.huobi.service.HuobiAccountService;
import com.mico.xchange.huobi.service.HuobiTradeService;
import com.mico.xchange.okcoin.OkCoinExchange;
import com.mico.xchange.okcoin.dto.trade.OkCoinTradeResult;
import com.mico.xchange.okcoin.service.OkCoinTradeServiceRaw;
import org.apache.mina.core.session.IoSession;

import java.io.IOException;
import java.math.BigDecimal;
import java.util.Date;
import java.util.HashMap;
import java.util.Map;
import java.util.UUID;

/**
 * Created by chenst on 2018/5/6.
 */
public class PlaceMarketOrderThread extends MicoThread{
    public PlaceMarketOrderThread(IoSession session, String message) {
        super(session, message);
    }


    @Override
    public Map doHuobiChange(JSONObject json)  throws Exception{
        Exchange exchange = ExchangeCacheUtils.getExchange(HuobiExchange.class.getName(), json.get("apiKey").toString(), json.get("secretKey").toString());
        HuobiTradeService tradeService = (HuobiTradeService)exchange.getTradeService();
        HuobiAccountService accountService = (HuobiAccountService)exchange.getAccountService();
        String id =  accountService.getAccounts()[0].getId()+"";
        MarketOrder marketOrder = initMarketOrder(json,id);
//        tradeService.verifyOrder(marketOrder);
        Map<String,String> retMap = new HashMap<String,String>();
        String resultMarket = null;
        if("1".equals(json.getString("hadax"))){
            resultMarket = tradeService.placeHadaxMarketOrder(marketOrder);
        }else{
            resultMarket = tradeService.placeMarketOrder(marketOrder);
        }
        retMap.put("result",resultMarket);
        return retMap;
    }

    @Override
    public Map doBinanceChange(JSONObject json)  throws Exception{
        Exchange exchange = ExchangeCacheUtils.getExchange(BinanceExchange.class.getName(), json.get("apiKey").toString(), json.get("secretKey").toString());
        BinanceTradeService tradeService = (BinanceTradeService)exchange.getTradeService();
        BinanceMarketDataService marketDataService = (BinanceMarketDataService)exchange.getMarketDataService();
        BinanceAccountService accountService = (BinanceAccountService)exchange.getAccountService();
        String id = accountService.getAccountInfo().getWallet().getId();

//        MarketOrder marketOrder = initMarketOrder(json, id);

        //币安下单originalAmount传交易币的数量，火币传交易金额
        String orderType = json.get("orderType").toString();
        if("00".equals(orderType)) {
            BigDecimal originalAmount = json.getBigDecimal("originalAmount");

            String baseSymbol = json.get("baseSymbol").toString();
            String counterSymbol = json.get("counterSymbol").toString();
            BigDecimal price = RedisUtils.getTicketPrice(json.getString("exchange"),json.getString("baseSymbol"),json.getString("counterSymbol"));
            Symbol[] symbols = marketDataService.getExchangeInfo().getSymbols();
            int scale = 0;
            for(Symbol symbol : symbols){
                if(symbol.getBaseAsset().toLowerCase().equals(baseSymbol.toLowerCase()) && symbol.getQuoteAsset().toLowerCase().equals(counterSymbol.toLowerCase())){
                    Filter[] filters = symbol.getFilters();
                    for (Filter filter : filters) {
                        if ("LOT_SIZE".equals(filter.getFilterType())) {
                            String stepSize = filter.getStepSize();
                            scale = getScale(stepSize);
                            break;
                        }
                    }
                }
            }
            BigDecimal quantity = originalAmount.divide(price, scale, BigDecimal.ROUND_HALF_DOWN);
            json.put("originalAmount", quantity);
        }


        MarketOrder marketOrder = initMarketOrder(json,id);
//        tradeService.verifyOrder(marketOrder);
        Map<String,String> retMap = new HashMap<String,String>();
        String resultMarket = tradeService.placeMarketOrder(marketOrder);
        retMap.put("result",resultMarket);
        return retMap;
    }

    private int getScale(String stepSize) {
        String var = stepSize.substring(stepSize.indexOf(".") + 1);
        if(var.indexOf("1")>=0){
            return (var.indexOf("1") + 1);
        }else{
            return 0;
        }
    }

    @Override
    public Map doChaoexChange(JSONObject json) throws Exception {
        throw new Exception("chaoex not imple");
    }

    @Override
    public Map doBitstampChange(JSONObject json) throws Exception {
        //初始化数据
        String orderType = json.get("orderType").toString();
        BigDecimal originalAmount = json.getBigDecimal("originalAmount");//交易币的数量
        String baseSymbol = json.get("baseSymbol").toString();
        String counterSymbol = json.get("counterSymbol").toString();
        CurrencyPair currencyPair = new CurrencyPair(baseSymbol,counterSymbol);
        BitstampAuthenticatedV2.Side side = "00".equals(orderType)?BitstampAuthenticatedV2.Side.buy:BitstampAuthenticatedV2.Side.sell;

        Exchange exchange = ExchangeFactory.INSTANCE.createExchange(BitstampExchange.class.getName(), json.get("apiKey").toString(), json.get("secretKey").toString());
        BitstampTradeServiceRaw tradeService = (BitstampTradeServiceRaw) exchange.getTradeService();
        BitstampOrder order = tradeService.placeBitstampMarketOrder(currencyPair,side,originalAmount);
        String orderId = ""+order.getId();
        Map<String,String> retMap = new HashMap<String,String>();

        retMap.put("result",orderId);
        return retMap;

    }

    @Override
    public Map doOkexChange(JSONObject json) throws Exception {
        //初始化数据
        String orderType = json.get("orderType").toString();
        BigDecimal originalAmount = json.getBigDecimal("originalAmount");//交易币的数量
        String baseSymbol = json.get("baseSymbol").toString();
        String counterSymbol = json.get("counterSymbol").toString();
        String symbol = counterSymbol.toLowerCase()+"_"+baseSymbol.toLowerCase();
        String tradeType = orderType.equals("00")?"buy_market":"sell_market";

        //现货交易
        Exchange exchange = ExchangeFactory.INSTANCE.createExchange(OkCoinExchange.class.getName(),json.get("apiKey").toString(), json.get("secretKey").toString());
        OkCoinTradeServiceRaw okCoinTradeServiceRaw = (OkCoinTradeServiceRaw)exchange.getTradeService();
        OkCoinTradeResult result = okCoinTradeServiceRaw.trade(symbol,tradeType,null,originalAmount.toPlainString());
        if(result.isResult()){
            Map<String,String> retMap = new HashMap<String,String>();
            retMap.put("result",result.getOrderId()+"");
            return retMap;
        }
        return null;
    }

    @Override
    public Map doFCoinExchange(JSONObject json) throws Exception {
        //初始化数据
        BigDecimal originalAmount = json.getBigDecimal("originalAmount");//交易币的数量
        String orderType = json.get("orderType").toString();
        FCoinSide tradeType = orderType.equals("00")?FCoinSide.buy :FCoinSide.sell;
        String baseSymbol = json.get("counterSymbol").toString();
        String counterSymbol = json.get("baseSymbol").toString();
        String symbol = counterSymbol.toLowerCase()+baseSymbol.toLowerCase();

        Exchange exchange = ExchangeFactory.INSTANCE.createExchange(FCoinExchange.class.getName(),json.get("apiKey").toString(), json.get("secretKey").toString());
        FCoinTradeServiceRaw tradeService = (FCoinTradeServiceRaw)exchange.getTradeService();
        String order_id = tradeService.placeMarketOrder(symbol,originalAmount,tradeType);
        Map<String,String> retMap = new HashMap<String,String>();
        retMap.put("result",order_id);
        return retMap;
    }

    public MarketOrder initMarketOrder(JSONObject json,String orderId){
        //初始化数据
        String orderType = json.get("orderType").toString();
        BigDecimal originalAmount = json.getBigDecimal("originalAmount");//买单时上传金额，买单上传数量
        String baseSymbol = json.get("baseSymbol").toString();
        String counterSymbol = json.get("counterSymbol").toString();
        MarketOrder marketOrder = new MarketOrder("00".equals(orderType)?Order.OrderType.BID:Order.OrderType.ASK,originalAmount,new CurrencyPair(baseSymbol,counterSymbol), orderId,new Date());
        return marketOrder;
    }
}
